home *** CD-ROM | disk | FTP | other *** search
/ SGI Freeware 1999 August / SGI Freeware 1999 August.iso / dist / fw_xemacs.idb / usr / freeware / lib / xemacs-20.4 / lisp / cc-mode / cc-styles.el.z / cc-styles.el
Encoding:
Text File  |  1998-05-21  |  24.9 KB  |  673 lines

  1. ;;; cc-styles.el --- support for styles in CC Mode
  2.  
  3. ;; Copyright (C) 1985,87,92,93,94,95,96,97,98 Free Software Foundation, Inc.
  4.  
  5. ;; Authors:    1992-1997 Barry A. Warsaw
  6. ;;             1987 Dave Detlefs and Stewart Clamen
  7. ;;             1985 Richard M. Stallman
  8. ;; Maintainer: cc-mode-help@python.org
  9. ;; Created:    22-Apr-1997 (split from cc-mode.el)
  10. ;; Version:    See cc-mode.el
  11. ;; Keywords:   c languages oop
  12.  
  13. ;; This file is part of GNU Emacs.
  14.  
  15. ;; GNU Emacs is free software; you can redistribute it and/or modify
  16. ;; it under the terms of the GNU General Public License as published by
  17. ;; the Free Software Foundation; either version 2, or (at your option)
  18. ;; any later version.
  19.  
  20. ;; GNU Emacs is distributed in the hope that it will be useful,
  21. ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
  22. ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  23. ;; GNU General Public License for more details.
  24.  
  25. ;; You should have received a copy of the GNU General Public License
  26. ;; along with GNU Emacs; see the file COPYING.  If not, write to the
  27. ;; Free Software Foundation, Inc., 59 Temple Place - Suite 330,
  28. ;; Boston, MA 02111-1307, USA.
  29.  
  30.  
  31.  
  32. (defconst c-style-alist
  33.   '(("gnu"
  34.      (c-basic-offset . 2)
  35.      (c-comment-only-line-offset . (0 . 0))
  36.      (c-offsets-alist . ((statement-block-intro . +)
  37.              (knr-argdecl-intro . 5)
  38.              (substatement-open . +)
  39.              (label . 0)
  40.              (statement-case-open . +)
  41.              (statement-cont . +)
  42.              (arglist-intro . c-lineup-arglist-intro-after-paren)
  43.              (arglist-close . c-lineup-arglist)
  44.              ))
  45.      (c-special-indent-hook . c-gnu-impose-minimum)
  46.      (c-comment-continuation-stars . "")
  47.      (c-hanging-comment-ender-p . t)
  48.      )
  49.     ("k&r"
  50.      (c-basic-offset . 5)
  51.      (c-comment-only-line-offset . 0)
  52.      (c-offsets-alist . ((statement-block-intro . +)
  53.              (knr-argdecl-intro . 0)
  54.              (substatement-open . 0)
  55.              (label . 0)
  56.              (statement-cont . +)
  57.              ))
  58.      )
  59.     ("bsd"
  60.      (c-basic-offset . 4)
  61.      (c-comment-only-line-offset . 0)
  62.      (c-offsets-alist . ((statement-block-intro . +)
  63.              (knr-argdecl-intro . +)
  64.              (substatement-open . 0)
  65.              (label . 0)
  66.              (statement-cont . +)
  67.              ))
  68.      )
  69.     ("stroustrup"
  70.      (c-basic-offset . 4)
  71.      (c-comment-only-line-offset . 0)
  72.      (c-offsets-alist . ((statement-block-intro . +)
  73.              (substatement-open . 0)
  74.              (label . 0)
  75.              (statement-cont . +)
  76.              ))
  77.      )
  78.     ("whitesmith"
  79.      (c-basic-offset . 4)
  80.      (c-comment-only-line-offset . 0)
  81.      (c-offsets-alist . ((statement-block-intro . +)
  82.              (knr-argdecl-intro . +)
  83.              (substatement-open . 0)
  84.              (label . 0)
  85.              (statement-cont . +)
  86.              ))
  87.  
  88.      )
  89.     ("ellemtel"
  90.      (c-basic-offset . 3)
  91.      (c-comment-only-line-offset . 0)
  92.      (c-hanging-braces-alist     . ((substatement-open before after)))
  93.      (c-offsets-alist . ((topmost-intro        . 0)
  94.                          (topmost-intro-cont   . 0)
  95.                          (substatement         . +)
  96.              (substatement-open    . 0)
  97.                          (case-label           . +)
  98.                          (access-label         . -)
  99.                          (inclass              . ++)
  100.                          (inline-open          . 0)
  101.                          ))
  102.      )
  103.     ("linux"
  104.      (c-basic-offset  . 8)
  105.      (c-comment-only-line-offset . 0)
  106.      (c-hanging-braces-alist . ((brace-list-open)
  107.                 (substatement-open after)
  108.                 (block-close . c-snug-do-while)))
  109.      (c-cleanup-list . (brace-else-brace))
  110.      (c-offsets-alist . ((statement-block-intro . +)
  111.              (knr-argdecl-intro     . 0)
  112.              (substatement-open     . 0)
  113.              (label                 . 0)
  114.              (statement-cont        . +)
  115.              ))
  116.      )
  117.     ("python"
  118.      (indent-tabs-mode . t)
  119.      (fill-column      . 72)
  120.      (c-basic-offset   . 8)
  121.      (c-offsets-alist  . ((substatement-open . 0)
  122.               (inextern-lang . 0)
  123.               (arglist-intro . +)
  124.               (knr-argdecl-intro . +)
  125.               ))
  126.      (c-hanging-braces-alist . ((brace-list-open)
  127.                 (brace-list-intro)
  128.                 (brace-list-close)
  129.                 (substatement-open after)
  130.                 (block-close . c-snug-do-while)
  131.                 ))
  132.      (c-comment-continuation-stars . "")
  133.      (c-hanging-comment-ender-p . nil)
  134.      (fill-column . 78)
  135.      )
  136.     ("java"
  137.      (c-basic-offset . 4)
  138.      (c-comment-only-line-offset . (0 . 0))
  139.      ;; the following preserves Javadoc starter lines
  140.      (c-hanging-comment-starter-p . nil)
  141.      (c-offsets-alist . ((inline-open . 0)
  142.              (topmost-intro-cont    . +)
  143.              (statement-block-intro . +)
  144.               (knr-argdecl-intro     . 5)
  145.               (substatement-open     . +)
  146.               (label                 . 0)
  147.               (statement-case-open   . +)
  148.               (statement-cont        . +)
  149.               (arglist-intro  . c-lineup-arglist-intro-after-paren)
  150.               (arglist-close  . c-lineup-arglist)
  151.               (access-label   . 0)
  152.              (inher-cont     . c-lineup-java-inher)
  153.              (func-decl-cont . c-lineup-java-throws)
  154.              ))
  155.  
  156.      )
  157.     )
  158.   "Styles of indentation.
  159. Elements of this alist are of the form:
  160.  
  161.   (STYLE-STRING [BASE-STYLE] (VARIABLE . VALUE) [(VARIABLE . VALUE) ...])
  162.  
  163. where STYLE-STRING is a short descriptive string used to select a
  164. style, VARIABLE is any Emacs variable, and VALUE is the intended value
  165. for that variable when using the selected style.
  166.  
  167. Optional BASE-STYLE if present, is a string and must follow
  168. STYLE-STRING.  BASE-STYLE names a style that this style inherits from.
  169. By default, all styles inherit from the \"cc-mode\" style, which is
  170. computed at run time.  Style loops generate errors.
  171.  
  172. Two variables are treated specially.  When VARIABLE is
  173. `c-offsets-alist', the VALUE is a list containing elements of the
  174. form:
  175.  
  176.   (SYNTACTIC-SYMBOL . OFFSET)
  177.  
  178. as described in `c-offsets-alist'.  These are passed directly to
  179. `c-set-offset' so there is no need to set every syntactic symbol in
  180. your style, only those that are different from the default.
  181.  
  182. When VARIABLE is `c-special-indent-hook', its VALUE is added to
  183. `c-special-indent-hook' using `add-hook'.  If VALUE is a list, each
  184. element of the list is added with `add-hook'.
  185.  
  186. Do not change this variable directly.  Use the function `c-add-style'
  187. to add new styles or modify existing styles (it is not a good idea to
  188. modify existing styles -- you should create a new style that inherits
  189. the existing style.")
  190.  
  191.  
  192. ;; Functions that manipulate styles
  193. (defun c-set-style-1 (conscell)
  194.   ;; Set the style for one variable
  195.   (let ((attr (car conscell))
  196.     (val  (cdr conscell)))
  197.     (cond
  198.      ;; first special variable
  199.      ((eq attr 'c-offsets-alist)
  200.       (mapcar
  201.        (function
  202.     (lambda (langentry)
  203.       (let ((langelem (car langentry))
  204.         (offset (cdr langentry)))
  205.         (c-set-offset langelem offset)
  206.         )))
  207.        val))
  208.      ;; second special variable
  209.      ((eq attr 'c-special-indent-hook)
  210.       (if (listp val)
  211.       (while val
  212.         (add-hook 'c-special-indent-hook (car val))
  213.         (setq val (cdr val)))
  214.     (add-hook 'c-special-indent-hook val)))
  215.      ;; all other variables
  216.      (t (set attr val)))
  217.     ))
  218.  
  219. (defun c-set-style-2 (style basestyles)
  220.   ;; Recursively set the base style.  If no base style is given, the
  221.   ;; default base style is "user" (a.k.a. "cc-mode") and the recursion
  222.   ;; stops.  Be sure to detect loops.
  223.   (let ((vars (cdr (or (assoc (downcase style) c-style-alist)
  224.                (assoc (upcase style) c-style-alist)
  225.                (assoc style c-style-alist)
  226.                (error "Undefined style: %s" style)))))
  227.     (if (not (string-equal style "user"))
  228.     (let ((base (if (stringp (car vars))
  229.             (prog1
  230.                 (downcase (car vars))
  231.               (setq vars (cdr vars)))
  232.               "user")))
  233.       (if (memq base basestyles)
  234.           (error "Style loop detected: %s in %s" base basestyles))
  235.       (c-set-style-2 base (cons base basestyles))))
  236.     (mapcar 'c-set-style-1 vars)))
  237.     
  238. (defvar c-set-style-history nil)
  239.  
  240. ;;;###autoload
  241. (defun c-set-style (stylename)
  242.   "Set CC Mode variables to use one of several different indentation styles.
  243. STYLENAME is a string representing the desired style from the list of
  244. styles described in the variable `c-style-alist'.  See that variable
  245. for details of setting up styles.
  246.  
  247. The variable `c-indentation-style' always contains the buffer's current
  248. style name."
  249.   (interactive (list (let ((completion-ignore-case t)
  250.                (prompt (format "Which %s indentation style? "
  251.                        mode-name)))
  252.                (completing-read prompt c-style-alist nil t
  253.                     (cons c-indentation-style 0)
  254.                     'c-set-style-history))))
  255.   (c-initialize-builtin-style)
  256.   (c-set-style-2 stylename nil)
  257.   (setq c-indentation-style stylename)
  258.   (c-keep-region-active))
  259.  
  260. ;;;###autoload
  261. (defun c-add-style (style descrip &optional set-p)
  262.   "Adds a style to `c-style-alist', or updates an existing one.
  263. STYLE is a string identifying the style to add or update.  DESCRIP is
  264. an association list describing the style and must be of the form:
  265.  
  266.   ([BASESTYLE] (VARIABLE . VALUE) [(VARIABLE . VALUE) ...])
  267.  
  268. See the variable `c-style-alist' for the semantics of BASESTYLE,
  269. VARIABLE and VALUE.  This function also sets the current style to
  270. STYLE using `c-set-style' if the optional SET-P flag is non-nil."
  271.   (interactive
  272.    (let ((stylename (completing-read "Style to add: " c-style-alist
  273.                      nil nil nil 'c-set-style-history))
  274.      (description (eval-minibuffer "Style description: ")))
  275.      (list stylename description
  276.        (y-or-n-p "Set the style too? "))))
  277.   (setq style (downcase style))
  278.   (let ((s (assoc style c-style-alist)))
  279.     (if s
  280.     (setcdr s (copy-alist descrip))    ; replace
  281.       (setq c-style-alist (cons (cons style descrip) c-style-alist))))
  282.   (and set-p (c-set-style style)))
  283.  
  284.  
  285.  
  286. (defconst c-offsets-alist
  287.   '((string                . -1000)
  288.     (c                     . c-lineup-C-comments)
  289.     (defun-open            . 0)
  290.     (defun-close           . 0)
  291.     (defun-block-intro     . +)
  292.     (class-open            . 0)
  293.     (class-close           . 0)
  294.     (inline-open           . +)
  295.     (inline-close          . 0)
  296.     (func-decl-cont        . +)
  297.     (knr-argdecl-intro     . +)
  298.     (knr-argdecl           . 0)
  299.     (topmost-intro         . 0)
  300.     (topmost-intro-cont    . 0)
  301.     (member-init-intro     . +)
  302.     (member-init-cont      . 0)
  303.     (inher-intro           . +)
  304.     (inher-cont            . c-lineup-multi-inher)
  305.     (block-open            . 0)
  306.     (block-close           . 0)
  307.     (brace-list-open       . 0)
  308.     (brace-list-close      . 0)
  309.     (brace-list-intro      . +)
  310.     (brace-list-entry      . 0)
  311.     (statement             . 0)
  312.     ;; some people might prefer
  313.     ;;(statement             . c-lineup-runin-statements)
  314.     (statement-cont        . +)
  315.     ;; some people might prefer
  316.     ;;(statement-cont        . c-lineup-math)
  317.     (statement-block-intro . +)
  318.     (statement-case-intro  . +)
  319.     (statement-case-open   . 0)
  320.     (substatement          . +)
  321.     (substatement-open     . +)
  322.     (case-label            . 0)
  323.     (access-label          . -)
  324.     (label                 . 2)
  325.     (do-while-closure      . 0)
  326.     (else-clause           . 0)
  327.     (comment-intro         . c-lineup-comment)
  328.     (arglist-intro         . +)
  329.     (arglist-cont          . 0)
  330.     (arglist-cont-nonempty . c-lineup-arglist)
  331.     (arglist-close         . +)
  332.     (stream-op             . c-lineup-streamop)
  333.     (inclass               . +)
  334.     (cpp-macro             . -1000)
  335.     (cpp-macro-cont        . c-lineup-dont-change)
  336.     (friend                . 0)
  337.     (objc-method-intro     . -1000)
  338.     (objc-method-args-cont . c-lineup-ObjC-method-args)
  339.     (objc-method-call-cont . c-lineup-ObjC-method-call)
  340.     (extern-lang-open      . 0)
  341.     (extern-lang-close     . 0)
  342.     (inextern-lang         . +)
  343.     (namespace-open        . 0)
  344.     (namespace-close       . 0)
  345.     (innamespace           . +)
  346.     (template-args-cont    . +)
  347.     )
  348.   "Association list of syntactic element symbols and indentation offsets.
  349. As described below, each cons cell in this list has the form:
  350.  
  351.     (SYNTACTIC-SYMBOL . OFFSET)
  352.  
  353. When a line is indented, CC Mode first determines the syntactic
  354. context of the line by generating a list of symbols called syntactic
  355. elements.  This list can contain more than one syntactic element and
  356. the global variable `c-syntactic-context' contains the context list
  357. for the line being indented.  Each element in this list is actually a
  358. cons cell of the syntactic symbol and a buffer position.  This buffer
  359. position is called the relative indent point for the line.  Some
  360. syntactic symbols may not have a relative indent point associated with
  361. them.
  362.  
  363. After the syntactic context list for a line is generated, CC Mode
  364. calculates the absolute indentation for the line by looking at each
  365. syntactic element in the list.  First, it compares the syntactic
  366. element against the SYNTACTIC-SYMBOL's in `c-offsets-alist'.  When it
  367. finds a match, it adds the OFFSET to the column of the relative indent
  368. point.  The sum of this calculation for each element in the syntactic
  369. list is the absolute offset for line being indented.
  370.  
  371. If the syntactic element does not match any in the `c-offsets-alist',
  372. an error is generated if `c-strict-syntax-p' is non-nil, otherwise the
  373. element is ignored.
  374.  
  375. Actually, OFFSET can be an integer, a function, a variable, or one of
  376. the following symbols: `+', `-', `++', `--', `*', or `/'.  These
  377. latter designate positive or negative multiples of `c-basic-offset',
  378. respectively: 1, -1, 2, -2, 0.5, and -0.5. If OFFSET is a function, it
  379. is called with a single argument containing the cons of the syntactic
  380. element symbol and the relative indent point.  The function should
  381. return an integer offset.
  382.  
  383. Here is the current list of valid syntactic element symbols:
  384.  
  385.  string                 -- inside multi-line string
  386.  c                      -- inside a multi-line C style block comment
  387.  defun-open             -- brace that opens a function definition
  388.  defun-close            -- brace that closes a function definition
  389.  defun-block-intro      -- the first line in a top-level defun
  390.  class-open             -- brace that opens a class definition
  391.  class-close            -- brace that closes a class definition
  392.  inline-open            -- brace that opens an in-class inline method
  393.  inline-close           -- brace that closes an in-class inline method
  394.  func-decl-cont         -- the region between a function definition's
  395.                            argument list and the function opening brace
  396.                            (excluding K&R argument declarations). In C, you
  397.                            cannot put anything but whitespace and comments
  398.                            between them; in C++ and Java, throws declarations
  399.                            and other things can appear in this context.
  400.  knr-argdecl-intro      -- first line of a K&R C argument declaration
  401.  knr-argdecl            -- subsequent lines in a K&R C argument declaration
  402.  topmost-intro          -- the first line in a topmost construct definition
  403.  topmost-intro-cont     -- topmost definition continuation lines
  404.  member-init-intro      -- first line in a member initialization list
  405.  member-init-cont       -- subsequent member initialization list lines
  406.  inher-intro            -- first line of a multiple inheritance list
  407.  inher-cont             -- subsequent multiple inheritance lines
  408.  block-open             -- statement block open brace
  409.  block-close            -- statement block close brace
  410.  brace-list-open        -- open brace of an enum or static array list
  411.  brace-list-close       -- close brace of an enum or static array list
  412.  brace-list-intro       -- first line in an enum or static array list
  413.  brace-list-entry       -- subsequent lines in an enum or static array list
  414.  statement              -- a C (or like) statement
  415.  statement-cont         -- a continuation of a C (or like) statement
  416.  statement-block-intro  -- the first line in a new statement block
  417.  statement-case-intro   -- the first line in a case \"block\"
  418.  statement-case-open    -- the first line in a case block starting with brace
  419.  substatement           -- the first line after an if/while/for/do/else
  420.  substatement-open      -- the brace that opens a substatement block
  421.  case-label             -- a `case' or `default' label
  422.  access-label           -- C++ private/protected/public access label
  423.  label                  -- any ordinary label
  424.  do-while-closure       -- the `while' that ends a do/while construct
  425.  else-clause            -- the `else' of an if/else construct
  426.  comment-intro          -- a line containing only a comment introduction
  427.  arglist-intro          -- the first line in an argument list
  428.  arglist-cont           -- subsequent argument list lines when no
  429.                            arguments follow on the same line as the
  430.                            arglist opening paren
  431.  arglist-cont-nonempty  -- subsequent argument list lines when at
  432.                            least one argument follows on the same
  433.                            line as the arglist opening paren
  434.  arglist-close          -- the solo close paren of an argument list
  435.  stream-op              -- lines continuing a stream operator construct
  436.  inclass                -- the construct is nested inside a class definition
  437.  cpp-macro              -- the start of a C preprocessor macro definition
  438.  cpp-macro-cont         -- the second and subsequent lines in a
  439.                            multi-line C preprocessor macro definition
  440.  friend                 -- a C++ friend declaration
  441.  objc-method-intro      -- the first line of an Objective-C method definition
  442.  objc-method-args-cont  -- lines continuing an Objective-C method definition
  443.  objc-method-call-cont  -- lines continuing an Objective-C method call
  444.  extern-lang-open       -- brace that opens an external language block
  445.  extern-lang-close      -- brace that closes an external language block
  446.  inextern-lang          -- analogous to `inclass' syntactic symbol,
  447.                            but used inside, e.g. extern \"C\" constructs
  448.  namespace-open         -- brace that opens a C++ namespace block
  449.  namespace-close        -- brace that closes a C++ namespace block
  450.  innamespace            -- analogous to `inextern-lang' syntactic
  451.                            symbol, but used inside C++ namespace constructs
  452.  template-args-cont     -- C++ template argument list continuations
  453. ")
  454.  
  455. (defun c-get-offset (langelem)
  456.   ;; Get offset from LANGELEM which is a cons cell of the form:
  457.   ;; (SYMBOL . RELPOS).  The symbol is matched against
  458.   ;; c-offsets-alist and the offset found there is either returned,
  459.   ;; or added to the indentation at RELPOS.  If RELPOS is nil, then
  460.   ;; the offset is simply returned.
  461.   (let* ((symbol (car langelem))
  462.      (relpos (cdr langelem))
  463.      (match  (assq symbol c-offsets-alist))
  464.      (offset (cdr-safe match)))
  465.     ;; offset can be a number, a function, a variable, or one of the
  466.     ;; symbols + or -
  467.     (cond
  468.      ((not match)
  469.       (if c-strict-syntax-p
  470.       (error "don't know how to indent a %s" symbol)
  471.     (setq offset 0
  472.           relpos 0)))
  473.      ((eq offset '+)         (setq offset c-basic-offset))
  474.      ((eq offset '-)         (setq offset (- c-basic-offset)))
  475.      ((eq offset '++)        (setq offset (* 2 c-basic-offset)))
  476.      ((eq offset '--)        (setq offset (* 2 (- c-basic-offset))))
  477.      ((eq offset '*)         (setq offset (/ c-basic-offset 2)))
  478.      ((eq offset '/)         (setq offset (/ (- c-basic-offset) 2)))
  479.      ((functionp offset)     (setq offset (funcall offset langelem)))
  480.      ((not (numberp offset)) (setq offset (symbol-value offset)))
  481.      )
  482.     (+ (if (and relpos
  483.         (< relpos (c-point 'bol)))
  484.        (save-excursion
  485.          (goto-char relpos)
  486.          (current-column))
  487.      0)
  488.        offset)))
  489.  
  490.  
  491. (defvar c-read-offset-history nil)
  492.  
  493. (defun c-read-offset (langelem)
  494.   ;; read new offset value for LANGELEM from minibuffer. return a
  495.   ;; legal value only
  496.   (let* ((oldoff (cdr-safe (assq langelem c-offsets-alist)))
  497.      (defstr (format "(default %s): " oldoff))
  498.      (errmsg (concat "Offset must be int, func, var, "
  499.              "or in [+,-,++,--,*,/] "
  500.              defstr))
  501.      (prompt (concat "Offset " defstr))
  502.      offset input interned raw)
  503.     (while (not offset)
  504.       (setq input (completing-read prompt obarray 'fboundp nil nil
  505.                    'c-read-offset-history)
  506.         offset (cond ((string-equal "" input) oldoff)  ; default
  507.              ((string-equal "+" input) '+)
  508.              ((string-equal "-" input) '-)
  509.              ((string-equal "++" input) '++)
  510.              ((string-equal "--" input) '--)
  511.              ((string-equal "*" input) '*)
  512.              ((string-equal "/" input) '/)
  513.              ((string-match "^-?[0-9]+$" input)
  514.               (string-to-int input))
  515.              ;; a symbol with a function binding
  516.              ((fboundp (setq interned (intern input)))
  517.               interned)
  518.              ;; a lambda function
  519.              ((c-safe (functionp (setq raw (read input))))
  520.               raw)
  521.              ;; a symbol with variable binding
  522.              ((boundp interned) interned)
  523.              ;; error, but don't signal one, keep trying
  524.              ;; to read an input value
  525.              (t (ding)
  526.                 (setq prompt errmsg)
  527.                 nil))))
  528.     offset))
  529.  
  530. ;;;###autoload
  531. (defun c-set-offset (symbol offset &optional add-p)
  532.   "Change the value of a syntactic element symbol in `c-offsets-alist'.
  533. SYMBOL is the syntactic element symbol to change and OFFSET is the new
  534. offset for that syntactic element.  Optional ADD says to add SYMBOL to
  535. `c-offsets-alist' if it doesn't already appear there."
  536.   (interactive
  537.    (let* ((langelem
  538.        (intern (completing-read
  539.             (concat "Syntactic symbol to change"
  540.                 (if current-prefix-arg " or add" "")
  541.                 ": ")
  542.             (mapcar
  543.              #'(lambda (langelem)
  544.              (cons (format "%s" (car langelem)) nil))
  545.              c-offsets-alist)
  546.             nil (not current-prefix-arg)
  547.             ;; initial contents tries to be the last element
  548.             ;; on the syntactic analysis list for the current
  549.             ;; line
  550.             (let* ((syntax (c-guess-basic-syntax))
  551.                (len (length syntax))
  552.                (ic (format "%s" (car (nth (1- len) syntax)))))
  553.               (cons ic 0))
  554.             )))
  555.       (offset (c-read-offset langelem)))
  556.      (list langelem offset current-prefix-arg)))
  557.   ;; sanity check offset
  558.   (or (eq offset '+)
  559.       (eq offset '-)
  560.       (eq offset '++)
  561.       (eq offset '--)
  562.       (eq offset '*)
  563.       (eq offset '/)
  564.       (integerp offset)
  565.       (functionp offset)
  566.       (boundp offset)
  567.       (error "Offset must be int, func, var, or in [+,-,++,--,*,/]: %s"
  568.          offset))
  569.   (let ((entry (assq symbol c-offsets-alist)))
  570.     (if entry
  571.     (setcdr entry offset)
  572.       (if add-p
  573.       (setq c-offsets-alist (cons (cons symbol offset) c-offsets-alist))
  574.     (error "%s is not a valid syntactic symbol." symbol))))
  575.   (c-keep-region-active))
  576.  
  577.  
  578.  
  579. (defun c-initialize-builtin-style ()
  580.   ;; Dynamically append the default value of most variables. This is
  581.   ;; crucial because future c-set-style calls will always reset the
  582.   ;; variables first to the `cc-mode' style before instituting the new
  583.   ;; style.  Only do this once!
  584.   (c-initialize-cc-mode t)
  585.   (or (assoc "cc-mode" c-style-alist)
  586.       (assoc "user" c-style-alist)
  587.       (let (copyfunc)
  588.     ;; use built-in copy-tree if its there.
  589.     (if (and (fboundp 'copy-tree)
  590.          (functionp (symbol-function 'copy-tree)))
  591.         (setq copyfunc (symbol-function 'copy-tree))
  592.       (setq copyfunc (lambda (tree)
  593.                (if (consp tree)
  594.                    (cons (funcall copyfunc (car tree))
  595.                      (funcall copyfunc (cdr tree)))
  596.                  tree))))
  597.     (c-add-style "user"
  598.              (mapcar
  599.               (function
  600.                (lambda (var)
  601.              (let ((val (symbol-value var)))
  602.                (cons var (if (atom val)
  603.                      val
  604.                        (funcall copyfunc val)
  605.                        ))
  606.                )))
  607.               '(c-backslash-column
  608.             c-basic-offset
  609.             c-cleanup-list
  610.             c-comment-only-line-offset
  611.             c-electric-pound-behavior
  612.             c-hanging-braces-alist
  613.             c-hanging-colons-alist
  614.             c-hanging-comment-starter-p
  615.             c-hanging-comment-ender-p
  616.             c-offsets-alist
  617.             )))
  618.     (c-add-style "cc-mode" '("user"))
  619.     ;; the default style is now GNU.  This can be overridden in
  620.     ;; c-mode-common-hook or {c,c++,objc,java}-mode-hook.
  621.     (c-set-style c-default-style)))
  622.   (if c-style-variables-are-local-p
  623.       (c-make-styles-buffer-local)))
  624.  
  625.  
  626. (defun c-make-styles-buffer-local (&optional this-buf-only-p)
  627.   "Make all CC Mode style variables buffer local.
  628. If you edit primarily one style of C (or C++, Objective-C, Java) code,
  629. you probably want style variables to be global.  This is the default.
  630.  
  631. If you edit many different styles of C (or C++, Objective-C, Java) at
  632. the same time, you probably want the CC Mode style variables to be
  633. buffer local.  If you do, then you will need to set any CC Mode style
  634. variables in a hook function (e.g. off of c-mode-common-hook), instead
  635. of at the top level of your ~/.emacs file.
  636.  
  637. This function makes all the CC Mode style variables buffer local.
  638. Call it after CC Mode is loaded into your Emacs environment.
  639. Conversely, set the variable `c-style-variables-are-local-p' to t in
  640. your .emacs file, before CC Mode is loaded, and this function will be
  641. automatically called when CC Mode is loaded.
  642.  
  643. Optional argument, when non-nil, means use `make-local-variable'
  644. instead of `make-variable-buffer-local'."
  645.   ;; style variables
  646.   (let ((func (if this-buf-only-p
  647.           'make-local-variable
  648.         'make-variable-buffer-local))
  649.     (varsyms '(c-offsets-alist
  650.            c-basic-offset
  651.            c-file-style
  652.            c-file-offsets
  653.            c-comment-only-line-offset
  654.            c-cleanup-list
  655.            c-hanging-braces-alist
  656.            c-hanging-colons-alist
  657.            c-hanging-comment-starter-p
  658.            c-hanging-comment-ender-p
  659.            c-backslash-column
  660.            c-label-minimum-indentation
  661.            c-indentation-style)))
  662.     (mapcar func varsyms)
  663.     ;; Hooks must be handled specially
  664.     (if this-buf-only-p
  665.     (make-local-hook 'c-special-indent-hook)
  666.       (make-variable-buffer-local 'c-special-indent-hook))
  667.     ))
  668.  
  669.  
  670.  
  671. (provide 'cc-styles)
  672. ;;; cc-styles.el ends here
  673.